home *** CD-ROM | disk | FTP | other *** search
/ SPACE 2 / SPACE - Library 2 - Volume 1.iso / magazi~1 / 226 / analog.49 / f8.ca < prev    next >
Encoding:
Text File  |  1986-10-14  |  14.0 KB  |  331 lines

  1.  
  2. /*****************************************************************
  3. *
  4. * f8.ca: additional subroutines for ST text screen dump:
  5. *        part 3 of 3.
  6. *        Megamax in-line version.
  7. *
  8. *
  9. ******************************************************************/
  10.  
  11.  
  12.  
  13. /****
  14. *
  15. * dump_line-- dump a line's worth of screen text data.
  16. *
  17. *    at entry:
  18. *              (a6) +  8 ->   point to begin from (byte address).
  19. *              (a6) + 12 ->   font header.
  20. *             [(a6) + 16 ->   ascii code returned by 'recognize'.]
  21. *              (a6) + 20 ->   bit offset of start point.
  22. *              (a6) + 24 ->   length of screen line in bytes.
  23. *              (a6) + 28 ->   space to save dumped codes.
  24. *
  25. *    internal usage:
  26. *              d0 -- miscellaneous & function return.
  27. *              d1 -- ascii code from 'recognize()'.
  28. *              d2 -- unused.
  29. *              d3 -- bit offset.
  30. *              d4 -- character cell width.
  31. *              d5 -- loop iteration counter.
  32. *              d6 -- unused.
  33. *              d7 -- hash index.
  34. *
  35. *              a0 -- pointer to collision list.
  36. *              a1 -- char byte address.
  37. *              a2 -- hash table base.
  38. *              a3 -- memory end address.
  39. *              a4 -- pointer to dump string space, or 
  40. *                 -- link register to Megamax C global variables.
  41. *              a5 -- font header pointer (not used during loop).
  42. *              a6 -- frame pointer.
  43. *  
  44. *    at exit:
  45. *              d0 == 0 if no error, -1 if error detected (i.e., first
  46. *                    character in line was not the same as that returned
  47. *                    by 'recognize').
  48. *              all other registers preserved.
  49. *
  50. *
  51. ****/
  52. dump_line:
  53.           link           A6,#-MAX_SCAN       ;frame pointer
  54.           movem.l        A0-A5/D1-D7,-(A7)   ;save registers
  55.  
  56.           move.l         #1,D6               ;init invert flag
  57.           movea.l        12(A6),A5           ;font header pointer
  58.           movea.l        8(A6),A1            ;start point
  59.           move.l         16(A6),D1           ;first ascii code-- we hope
  60.           move.l         20(A6),D3           ;bit offset of start
  61.           move.l         A1,-(A7)            ;push byte address
  62.           bsr            find_end            ;find end address of line
  63.           movea.l        (A7)+,A3            ;do it
  64.           move.l         #-1,D0              ;get a4
  65.           bsr            reg_a4              ;do it
  66.           movea.l        hash_table(A4),A2   ;hash table base
  67.           
  68.           movea.l        28(A6),A4           ;save dump space
  69.  
  70.           move.l         #0,D0               ;clear registers
  71.           move.l         #0,D2
  72.           move.l         #0,D4
  73.           move.l         #0,D5
  74.           move.l         #0,D7
  75.           move.w         BIG_CELL_WD(A5),D4  ;char cell width
  76.  
  77. dump_l_loop:
  78.           move.l         A4,-(A7)            ;save a4
  79.           move.l         #-1,D0              ;get link a4 (I hate this)
  80.           bsr            reg_a4              ;do it
  81.           move.l         D6,-(A7)            ;invert flag
  82.           move.l         resolution(A4),-(A7)    ;scan length
  83.           move.l         D3,-(A7)            ;bit offset
  84.           pea            -MAX_SCAN(A6)       ;space for scan slices
  85.           move.l         A5,-(A7)            ;font header
  86.           move.l         A1,-(A7)            ;byte address current char
  87.           bsr            make_slices         ;get hash value in d7
  88.           adda.l         #24,A7              ;pop args
  89.           movea.l        (A7)+,A4            ;restore a4
  90.  
  91.           mulu           #HASH_IX,D7         ;make it an index
  92.           tst.l          2(A2,D7.l)          ;test for collision
  93.           beq            d_l_no_coll         ;if none
  94.           bmi            dump_l_retry        ;if bad hash element
  95.           movea.l        2(A2,D7.l),A0       ;else get pointer
  96.  
  97.           pea            -MAX_SCAN(A6)       ;push scan vals list
  98.           move.l         A0,-(A7)            ;push start of collision list
  99.           bsr            find_collide        ;find a match
  100.           addq.l         #8,A7               ;pop args
  101.           tst.l          D0                  ;error?
  102.           bne.s          d_l_process         ;if not, d0.w has code
  103. d_l_no_coll:
  104.           clr.l          D0                  ;clear for word
  105.           move.w         0(A2,D7.l),D0       ;default code
  106.  
  107. /* process the code                          */
  108. /* first, double check:                      */
  109. d_l_process:
  110.           cmp.b          #FIRST_VALID,D0     ; < lowest valid char?
  111.           bmi            dump_l_retry        ;reject invalid char
  112.           cmp.b          #LAST_ASCII,D0      ; > highest valid char?
  113.           bgt            dump_l_retry        ;reject invalid char
  114. d_l_insert:
  115.           move.b         D0,(A4)+            ;save the code
  116.  
  117.           cmpi.l         #1,D6               ;was this an invert?
  118.           beq.s          d_l_ninv            ;if not
  119.           add.l          #-1,D6              ;else don't invert any more
  120.  
  121. d_l_ninv:
  122. /* now increment to next char cell           */
  123.           add.l          D4,D3               ;add cell width to bit offset
  124. d_l_continue:
  125.           cmp.l          #BYTESIZE,D3        ; < byte ?
  126.  
  127.           bmi            d_l_002             ;if so, continue at same addr
  128.           bne            d_l_003             ;if not byte-aligned result
  129.           clr.l          D3                  ;else make offset = 0
  130.           bra            d_l_004             ;and continue
  131. d_l_003:
  132.           sub.l          #BYTESIZE,D3        ;subtract one byte size
  133. d_l_004:
  134.           addq.l         #1,A1               ;increment byte address   
  135. d_l_002:
  136.           addq.l         #1,D5               ;iteration counter
  137.           cmpa.l         A1,A3               ;at end?
  138.           beq            dump_exit           ;if so
  139.           bra            dump_l_loop         ;else continue            
  140. dump_exit:
  141.           move.l         #0,D0               ;success code
  142.  
  143. dump_l_exit:
  144.           move.b         #NULL,(A4)          ;mark end of string
  145.           movem.l        (A7)+,A0-A5/D1-D7   ;restore registers
  146.           unlk           A6                  ;deallocate frame
  147.           rts
  148.  
  149. /* next couple of lines are meaningless now  */
  150. dump_l_retry:
  151.           addq.l         #1,D3               ;so try next bit offset
  152.           cmp.l          #RETRIES,D5         ;...for a byte or so
  153.           bmi            d_l_continue        ;do it
  154.           move.l         A4,-(A7)            ;save dump space pointer
  155.           move.l         #-1,D0              ;get link register
  156.           bsr            reg_a4              ;do it
  157.           addq.l         #1,hash_errors(A4)  ;else inc hash error count
  158.           movea.l        (A7)+,A4            ;recover dump space pointer
  159.  
  160. /* following is designed to handle character cell where cursor  */
  161. /*   happens to be.                                             */
  162.  
  163.           tst.l          D6                  ;inverted already?
  164.           bmi.s          bad_inv             ;if so, leave
  165.           add.l          #-1,D6              ;else decrement
  166.           bra            dump_l_loop         ;and try again
  167. bad_inv:
  168.           move.l         #-1,D0              ;error code
  169.           bra            dump_l_exit         ;leave
  170.  
  171.  
  172. /****
  173. *
  174. * find_end-- return end address of current screen line.
  175. *
  176. *    at entry:
  177. *              (a6) +  8 ->   current byte address.
  178. *              all other parms are values from the data or bss segments!
  179. *
  180. *    at exit:
  181. *              (a6) +  8 ->   end address, current line.
  182. *              all other registers preserved.
  183. *
  184. *
  185. ****/
  186. find_end:
  187.           link           A6,#0               ;frame pointer
  188.           movem.l        D0-D1/A4,-(A7)      ;save registers
  189.  
  190.           move.l         #-1,D0              ;get a4
  191.           bsr            reg_a4              ;do it
  192.           move.l         8(A6),D0            ;get current address
  193. #ifdef SC_IMAGE
  194.           sub.l          base(A4),D0         ; - base = logical address
  195.           move.l         resolution(A4),D1   ;get resolution
  196.           divu           D1,D0               ;logical address / resolution
  197.           mulu           D1,D0               ;quotient * resolution = start
  198.           add.l          D1,D0               ; + resolution = logical end 
  199.           add.l          base(A4),D0         ; + base = physical end
  200. #endif
  201. #ifdef NO_IMAGE
  202.           add.l          resolution(A4),D0   ;find end
  203. #endif
  204.           move.l         D0,8(A6)            ;put result on stack
  205.  
  206.           movem.l        (A7)+,D0-D1/A4      ;restore registers
  207.           unlk           A6                  ;deallocate frame pointer
  208.           rts
  209.  
  210.  
  211. /****
  212. *
  213. * set_window-- set up system variables for dump window coordinates.
  214. *
  215. *    at entry:
  216. *              (a6) +  8 ->   window height.
  217. *              (a6) + 12 ->   window width.
  218. *              (a6) + 16 ->   top left y-coordinate.
  219. *              (a6) + 20 ->   top left x-coordinate.
  220. *              (a6) + 24 ->   scan line length (== resolution).
  221. *              (a6) + 28 ->   start address storage area.
  222. *              (a6) + 32 ->   font header.
  223. *
  224. *    at exit:
  225. *              system variables are set to correct values.
  226. *              registers are preserved.
  227. *
  228. *
  229. ****/
  230. set_window:
  231.           link           A6,#0               ;frame pointer
  232.           movem.l        D0-D2/A0-A2/A4/A5,-(A7)      ;save registers
  233.  
  234.           move.l         #-1,D0              ;get a4
  235.           bsr            reg_a4              ;do it
  236.           movea.l        32(A6),A5           ;font header
  237.  
  238.           move.w         #3,-(A7)            ;code = get logbase
  239.           trap           #14                 ;do it
  240.           addq.l         #2,A7               ;pop arg
  241.  
  242.           move.l         D0,-(A7)            ;save orig screen base
  243.           move.l         16(A6),D1           ;get y coordinate
  244.  
  245.           move.l         y_align(A4),D0      ;get alignment factor
  246.           divu           D0,D1               ;divide y-coord by it
  247.           mulu           D0,D1               ;mult result by factor                    
  248.  
  249.           move.l         24(A6),D0           ;get scan line length
  250.           mulu           D0,D1               ; == logical pixel position
  251.           add.l          (A7)+,D1            ; == start row on screen
  252.           andi.l         #-2,D1              ;else ensure even number
  253.           move.l         D1,screen_base(A4)  ;save it     
  254.  
  255. #ifdef SC_IMAGE
  256.           move.l         chunk(A4),base(A4)  ;base of storage area
  257. #endif
  258. #ifdef NO_IMAGE
  259.           move.l         D1,base(A4)         ;direct from screen
  260. #endif
  261.  
  262.           move.l         8(A6),screen_height(A4) ;nr of scan lines to save
  263.  
  264.           move.l         20(A6),D1           ;x coordinate
  265.           divu           #BYTESIZE,D1        ;as byte address
  266.           swap           D1                  ;access remainder
  267.           move.w         D1,xshift(A4)       ;save it
  268.           swap           D1                  ;get quotient again
  269.           andi.l         #0xffff,D1          ;discard remainder
  270.  
  271.           move.l         D1,front(A4)        ; == front line offset
  272.  
  273.           move.l         D1,-(A7)            ;save 'front'
  274.           move.l         12(A6),D1           ;width of line
  275.           divu           #BYTESIZE,D1        ;as byte address
  276.           andi.l         #0xffff,D1          ;discard remainder
  277.           add.l          (A7)+,D1            ; + 'front' == end                      
  278.           sub.l          D1,D0               ;subtract from scan length
  279.  
  280.           move.l         D0,back(A4)         ; == back line offset
  281.  
  282.           add.l          front(A4),D0        ;add front to back offset
  283.           move.l         resolution(A4),D1   ;get old byte length
  284.           sub.l          D0,D1               ;subtract offsets
  285.           move.l         D1,resolution(A4)   ; == new resolution
  286.  
  287.           clr.l          D0                  ;clear for word
  288.           move.w         FORM_HEIGHT(A5),D0  ;char scan height
  289.           add.w          form_inc(A4),D0     ; + user-requested inc
  290.           move.l         D0,form_ht(A4)      ;effective scan height
  291.           mulu           D0,D1               ; * resolution = text line len
  292.           move.l         D1,line_size(A4)    ;save it
  293.  
  294.           move.l         scrn_text(A4),D1    ;full screen line byte length
  295.           mulu           D0,D1               ; * cell height
  296.           move.l         D1,scrn_size(A4)    ; == screen text line 
  297.  
  298.           move.l         8(A6),D1            ;get window height
  299.           divu           D0,D1               ;divide by cell height
  300.           andi.l         #0xffff,D1          ;discard remainder
  301. /* unscale     */
  302.           cmpi.l         #4,res_ix(A4)       ;medium res?
  303.           bne.s          sw_notmed           ;if not
  304.           lsr.l          #1,D1               ;else unscale line count
  305. sw_notmed:
  306.           cmpi.l         #0,res_ix(A4)       ;low res?
  307.           bne.s          sw_notlow           ;if not
  308.           lsr.l          #2,D1               ;else unscale line count
  309. sw_notlow:
  310.           move.l         D1,line_count(A4)   ; == number of text lines
  311.  
  312.           move.l         8(A6),D1            ;window height
  313.           move.l         resolution(A4),D0   ;wind line length in bytes
  314.           mulu           D0,D1               ;byte size of window
  315.           move.l         D1,-(A7)            ;save it
  316.           lsr.l          #1,D1               ; / 2 == word size
  317.           move.l         D1,screen_size(A4)  ;save it
  318.           move.l         (A7)+,D1            ;recover size in bytes
  319. #ifdef NO_IMAGE
  320.           move.l         #SMALL_SCRN,D1      ;
  321. #endif          
  322.           add.l          base(A4),D1         ; == phys addr last byte
  323.           move.l         D1,last(A4)         ;save it
  324.           move.l         D1,chunk_end(A4)    ;twice
  325.  
  326.           movem.l        (A7)+,D0-D2/A0-A2/A4/A5    ;restore registers
  327.           unlk           A6                  ;deallocate frame
  328.           rts                                ;dummy comment
  329.  
  330.  
  331.